import 'package:flutter/material.dart';
import 'package:dio/dio.dart';
import 'dart:convert';
import 'package:flutter_auth/constant/globals.dart' as globals;
import '../common/router.dart';
import 'package:flutter_styled_toast/flutter_styled_toast.dart';

/*
 * 网络请求管理类
 */
class DioManager {
  static DioManager _instance;

  static DioManager resetInstance() {
    _instance = null;
  }

  static DioManager getInstance() {
    if (_instance == null) {
      _instance = DioManager();
    }
    return _instance;
  }

  Dio dio = new Dio();
  DioManager() {
    // Set default configs
    dio.options.headers = {};
    if (globals.header['userId'] != null) {
      dio.options.headers['token'] = globals.header['token'];
      dio.options.headers['Cookie'] = globals.header['Cookie'];
      dio.options.headers['userId'] = globals.header['userId'];
      dio.options.headers['userName'] = globals.header['userName'];
    }
    dio.options.connectTimeout = 5000;
    dio.options.receiveTimeout = 3000;
  }

  //get请求
  get(String url, Map<String, dynamic> params) async {
    return _requstHttp(url, 'get', params);
  }

  //post请求
  post(String url, params) async {
    return _requstHttp(url, "post", params);
  }

  _requstHttp(String url, [String method, Map<String, dynamic> params]) async {
    Response response;
    try {
      if (method == 'get') {
        if (params != null) {
          response = await dio.get(url, queryParameters: params);
        } else {
          response = await dio.get(url);
        }
      } else if (method == 'post') {
        if (params != null) {
          response = await dio.post(url, data: params);
        } else {
          response = await dio.post(url);
        }
      }
    } on DioError catch (error) {
      // 请求错误处理
      Response errorResponse;
      if (error.response != null) {
        errorResponse = error.response;
      } else {
        errorResponse = new Response(statusCode: 666);
      }
      // 请求超时
      if (error.type == DioErrorType.CONNECT_TIMEOUT) {
        errorResponse.statusCode = ResultCode.CONNECT_TIMEOUT;
      }
      // 一般服务器错误
      else if (error.type == DioErrorType.RECEIVE_TIMEOUT) {
        errorResponse.statusCode = ResultCode.RECEIVE_TIMEOUT;
      }
      return {'state': false, 'msg': '请求超时'};
    }
    if (response.data != null && !response.data['state']) {
      var context = Router.navigatorKey.currentState.overlay.context;
      showToast(
        response.data['msg'],
        context: context,
        animation: StyledToastAnimation.slideFromTop,
        textStyle: TextStyle(color: Colors.red, fontSize: 16),
        reverseAnimation: StyledToastAnimation.slideToTop,
        startOffset: Offset(0.0, 3.0),
        reverseEndOffset: Offset(0.0, 3.0),
        position: StyledToastPosition.bottom,
        duration: Duration(seconds: 4),
        animDuration: Duration(seconds: 1),
        curve: Curves.elasticOut,
        reverseCurve: Curves.fastOutSlowIn,
      );
    }
    if (response.data['code'] == 1000) {
      Router.navigatorKey.currentState
          .pushNamedAndRemoveUntil("/", ModalRoute.withName("/"));
      return {'state': false, 'msg': '登录过期'};
    }
    String dataStr = json.encode(response.data);
    Map<String, dynamic> dataMap = json.decode(dataStr);
    return dataMap;
  }
}

/*
 * dio网络请求失败的回调错误码 
 */
class ResultCode {
  //正常返回是1
  static const SUCCESS = 1;

  //异常返回是0
  static const ERROR = 1;

  /// When opening  url timeout, it occurs.
  static const CONNECT_TIMEOUT = -1;

  ///It occurs when receiving timeout.
  static const RECEIVE_TIMEOUT = -2;

  /// When the server response, but with a incorrect status, such as 404, 503...
  static const RESPONSE = -3;

  /// When the request is cancelled, dio will throw a error with this type.
  static const CANCEL = -4;

  /// read the DioError.error if it is not null.
  static const DEFAULT = -5;
}
